<?php
// +----------------------------------------------------------------------
// | ManniuRead
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://manniuyun.com All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: heitao <read@manniuyun.com>
// +----------------------------------------------------------------------

namespace app\book\controller;

use app\book\base\BookFrontBase;

use think\Cache;
use app\member\model\Member;
use app\book\model\Book as BookModel;
use app\book\model\Chapter as ChapterModel;
use app\book\model\ChapterData;
use app\book\model\BookBuy;
use app\book\model\BookBookcases;
use app\book\model\BookAutoSubscription;
use think\exception\HttpException;

class Book extends BookFrontBase
{
    /**
     * 书库
     * @access public
     * @return \think\Response
     */
    public function all()
    {
        $list = BookModel::search($this->request->param());
        // 模板变量赋值
        $this->assign([
            'seo_title' => '书库',
            'seo_keywords' => '',
            'seo_description' => '',
            'list' => $list
        ]);
        return $this->getTemplate();
    }

    /**
     * 排行
     * @access public
     * @return \think\Response
     */
    public function top()
    {
        // 模板变量赋值
        $this->assign([
            'seo_title' => '排行',
            'seo_keywords' => '',
            'seo_description' => ''
        ]);
        return $this->getTemplate();
    }

    /**
     * 图书信息页
     * @access public
     * @param int $bid 图书ID
     * @return \think\Response
     */
    public function bookInfo($bid = 0, BookModel $book, ChapterModel $chapter)
    {
        // 判断参数是否合法
        $bid = (int)$bid;
        if (!$bid) {
            throw new HttpException(404, '缺少参数：bid');
        }
        // 读取图书信息
        $book = $book->getBook($bid);
        if (!$book) {
            throw new HttpException(404, '图书不存在');
        }
        // 读取章节列表
        $chapters = $chapter->getChapterList($bid);
        $last_chapter = is_array($chapters) && $chapters ? end($chapters) : '';
        // 模板变量赋值
        $this->assign($book);
        $this->assign([
            'seo_title' => $book['name'],
            'seo_keywords' => '',
            'seo_description' => str_replace("\r\n", '', $book['intro']),
            'last_chapter' => $last_chapter,
            'last_read_chapter' => $this->getReadRecord($book['id'], $chapter)
        ]);
        return $this->getTemplate();
    }

    /**
     * 图书章节列表页
     * @access public
     * @param int $bid 图书ID
     * @return \think\Response
     */
    public function chapterList($bid = 0, BookModel $book, ChapterModel $chapter)
    {
        // 判断参数是否合法
        $bid = (int)$bid;
        if (!$bid) {
            throw new HttpException(404, '缺少参数：bid');
        }
        // 读取图书信息
        $book = $book->getBook($bid);
        if (!$book) {
            throw new HttpException(404, '图书不存在');
        }
        // 读取章节列表
        $chapters = $chapter->getChapterList($bid);
        $last_chapter = is_array($chapters) && $chapters ? end($chapters) : '';
        // 模板变量赋值
        $this->assign([
            'seo_title' => $book['name'] . '_章节列表',
            'seo_keywords' => '',
            'seo_description' => str_replace("\r\n", '', $book['intro']),
            'last_chapter' => $last_chapter,
            'last_read_chapter' => $this->getReadRecord($book['id'], $chapter),
            'book' => $book,
            'list' => $chapters
        ]);
        return $this->getTemplate();
    }

    /**
     * 章节内容页
     * @access public
     * @param int $bid 图书ID
     * @param int $cid 章节ID
     * @return \think\Response
     */
    public function chapter($bid = 0, $cid = 0, BookModel $book, ChapterModel $chapter, ChapterData $chapter_data, BookBuy $book_buy)
    {
        // 判断参数是否合法
        $bid = (int)$bid;
        $cid = (int)$cid;
        if (!$bid || !$cid) {
            throw new HttpException(404, '缺少参数：bid或cid');
        }
        // 读取图书信息
        $book = $book->getBook($bid);
        if (!$book) {
            throw new HttpException(404, '图书不存在');
        }
        // 读取章节基础信息
        $chapter_info = $chapter->getChater($cid);
        $chapter_info['content'] = '';
        if (!$chapter_info) {
            throw new HttpException(404, '章节不存在');
        }

        $is_chapter_buy = false;                    // 章节是否购买标识
        $is_auto_subscription = false;              // 章节是否自动订阅标识
        $fc_auto_subscription = false;              // 强制关闭当前图书自动订阅功能标识
        // 判断是否登录
        if ($this->uid) {
            if ($chapter_info['charge']) { // 判断章节是否收费
                $is_chapter_buy = $book_buy->checkBuy($this->uid, $bid, $cid);
                if ($is_chapter_buy) {
                    $this->saveReadingRecord($bid, $cid); // 已购买此章节，更新最新阅读记录
                } else {
                    // 检查用户是否开启本书自动订阅
                    $book_as = new BookAutoSubscription;
                    $is_as = $book_as->checkAutoSubscription($this->uid, $bid);
                    if ($is_as) {
                        $is_auto_subscription = true;
                        $member = Member::get($this->uid);
                        // 获取章节价格
                        $chapter_price = (int)$chapter->where(['book_id' => $bid, 'id' => $cid, 'charge' => 1, 'status' => 1])->value('price');
                        if ($chapter_price === 0) {
                            // 章节价格为0时，标识为已购买，不记录
                            $is_chapter_buy = true;
                        } elseif ($chapter_price > (int)$member->read_money) {
                            // 用户余额不足时，强制关闭本书自动订阅功能
                            $book_as = $book_as->where(['uid' => $this->uid, 'book_id' => $bid])->find();
                            if ($book_as) {
                                $book_as->delete();
                            }
                            $fc_auto_subscription = true;
                        } elseif ((int)$member->read_money >= $chapter_price && $chapter_price >= 1) {
                            // 扣取阅读币
                            $member->read_money = (int)$member->read_money - $chapter_price;
                            $member->save();
                            // 保存购买记录
                            $book_buy->saveBuy([
                                'uid' => $this->uid,
                                'book_id' => $bid,
                                'chapter_id' => $cid,
                                'buy_price' => $chapter_price
                            ]);
                            // 标识为已购买
                            $is_chapter_buy = true;
                        }
                    }
                }
            } else {
                // 章节不收费，更新最新阅读记录
                $this->saveReadingRecord($bid, $cid);
            }
        }
        // 获取章节内容
        if ($is_chapter_buy || !$chapter_info['charge']) {
            $chapter_data_content = $chapter_data->getChapterData($cid);
            $chapter_info['content'] = isset($chapter_data_content['content']) ? $chapter_data_content['content'] : '';
        }
        // 模板变量赋值
        $this->assign([
            'seo_title' => $chapter_info['chapter_name'] . '_' . $book['name'],
            'seo_keywords' => $chapter_info['chapter_name'] . ',' . $book['name'],
            'seo_description' => str_replace("\r\n", '', $book['intro']),
            'book' => $book,
            'chapter' => $chapter_info,
            'is_chapter_buy' => $is_chapter_buy,
            'is_auto_subscription' => $is_auto_subscription,
            'fc_auto_subscription' => $fc_auto_subscription
        ]);
        return $this->getTemplate();
    }

    /**
     * 章节订阅
     * @access public
     * @param int $bid 图书ID
     * @param int $cid 章节ID
     * @return mixed
     */
    public function subscription($bid = 0, $cid = 0)
    {
        $bid = (int)$bid;
        $cid = (int)$cid;
        if (!$bid || !$cid) {
            return json(['status' => 0, 'msg' => '订阅参数错误']);
        }
        if (!$this->uid) {
            return json(['status' => 0, 'msg' => '请登录后再执行订阅操作']);
        }
        if (BookBuy::get(['uid' => $this->uid, 'book_id' => $bid, 'chapter_id' => $cid])) {
            return json(['status' => 0, 'msg' => '请勿重复订阅章节']);
        }
        // 获取会员信息
        $member_info = Member::get($this->uid);
        if (!$member_info) {
            return json(['status' => 0, 'msg' => '会员信息不存在，请尝试退出后重新登录']);
        }
        // 获取图书信息
        $book = new BookModel;
        $book = $book->getBook($bid);
        if (!$book) {
            return json(['status' => 0, 'msg' => '图书不存在']);
        }
        // 获取章节收费价格
        $chapter = ChapterModel::get(function ($query) use ($bid, $cid) {
            $query->field('charge,price')->where(['book_id' => $bid, 'id' => $cid, 'charge' => 1, 'status' => 1]);
        });
        if (!$chapter) {
            return json(['status' => 0, 'msg' => '免费章节无需订阅或章节不存在']);
        }
        // 如果章节阅读币收费价格高于会员剩余阅读币，则提示余额不足
        if ((int)$chapter['price'] > (int)$member_info->read_money) {
            return json(['status' => 0, 'msg' => '阅读币余额不足，请充值']);
        } else {
            // 扣取会员阅读币
            $member_info->read_money = (int)$member_info->read_money - (int)$chapter->price;
            $member_info->save();
            // 保存购买记录
            BookBuy::create([
                'uid' => $this->uid,
                'book_id' => $bid,
                'chapter_id' => $cid,
                'buy_price' => (int)$chapter->price
            ]);
            // 更新购买记录的缓存
            Cache::set('book_buy_' . $this->uid . '_bid_' . $bid . '_cid_' . $cid, 'Y');
            return json(['status' => 1, 'msg' => '订阅成功']);
        }
    }

    /**
     * 保存会员阅读记录
     * @access public
     * @param int $bid 图书ID
     * @param int $cid 章节ID
     * @param bool $imposed 是否强制加入书架
     * @return void
     */
    protected function saveReadingRecord($bid = 0, $cid = 0, $imposed = false)
    {
        $bid = (int)$bid;
        $cid = (int)$cid;
        if ($bid && $cid) {
            $bookcases_cache = Cache::get('bookcases_uid_' . $this->uid);
            // N代表null,表示最新缓存为空
            if ($bookcases_cache !== 'N') {
                if (isset($bookcases_cache[$bid])) {
                    if ($bookcases_cache[$bid]['lrc_id'] != $cid) {
                        $bookcases_cache[$bid]['lrc_id'] = $cid;
                        Cache::set('bookcases_uid_' . $this->uid, $bookcases_cache);
                        $bookcase = BookBookcases::get(['uid' => $this->uid, 'book_id' => $bid]);
                        if ($bookcase) {
                            if ($bookcase->lrc_id != $cid) {
                                $bookcase->lrc_id = $cid;
                                $bookcase->save();
                            }
                        }
                    }
                } else {
                    $bookcase = BookBookcases::get(['uid' => $this->uid, 'book_id' => $bid]);
                    if ($bookcase) {
                        if ($bookcase->lrc_id != $cid) {
                            $bookcase->lrc_id = $cid;
                            $bookcase->save();
                        }
                    }
                    // 更新此用户的书架缓存
                    BookBookcases::updateBookcaseCacheByUid($this->uid);
                    $bookcases_cache = Cache::get('bookcases_uid_' . $this->uid);
                    if ($bookcases_cache) {
                        Cache::set('bookcases_uid_' . $this->uid, 'N');
                    }
                }
            }
        }
    }

    /**
     * 获取会员阅读记录
     * @access public
     * @param int $bid 图书ID
     * @return mixed
     */
    protected function getReadRecord($bid = 0, $chapter)
    {
        $bid = (int)$bid;
        $last_read_chapter = null;
        if ($this->uid && $bid) {
            // 查询阅读记录
            $bookcase = BookBookcases::get(['uid' => $this->uid, 'book_id' => $bid]);
            if ($bookcase) {
                // 读取章节列表
                $chapters = $chapter->getChapterList($bookcase->book_id);
                $last_read_chapter = isset($chapters[$bookcase->lrc_id]) ? $chapters[$bookcase->lrc_id] : null;
            }
        }
        return $last_read_chapter;
    }
}
